package me.zhengjie.modules.hanzi.controller;

import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import me.zhengjie.modules.hanzi.exception.ImageProcessingException;
import me.zhengjie.modules.hanzi.service.HanziAiScoreService;
import me.zhengjie.modules.hanzi.service.HanziScoreService;
import me.zhengjie.modules.hanzi.utils.ImageDebugUtils;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.util.HashMap;
import java.util.Map;

/**
 * 汉字评分控制器
 */
@RestController
@RequiredArgsConstructor
@Tag(name = "汉字评分管理")
@RequestMapping("/api/hanzi-score")
@Slf4j
public class HanziScoreController {

    private final HanziScoreService hanziScoreService;
    private final HanziAiScoreService hanziAiScoreService;

    /**
     * 对用户手写汉字进行智能评分（结合传统算法和AI评分）
     * @param standardChar 标准汉字
     * @param userImage 用户手写汉字图片
     * @return 智能评分结果
     */
    @PostMapping("/score")
    @Operation(summary = "对用户手写汉字进行智能评分")
    public ResponseEntity<Map<String, Object>> scoreHandwriting(
            @Parameter(description = "标准汉字", required = true)
            @RequestParam("standardImage") String standardChar,
            @Parameter(description = "用户手写汉字图片", required = true)
            @RequestParam("userImage") MultipartFile userImage) {
        
        // 验证文件是否为空
        if (userImage.isEmpty()) {
            return new ResponseEntity<>(Map.of("error", "请提供用户手写汉字图片"), HttpStatus.BAD_REQUEST);
        }
        
        String userContentType = userImage.getContentType();
        
        if (userContentType == null || (!userContentType.startsWith("image/"))) {
            return new ResponseEntity<>(Map.of("error", "请提供有效的图片文件"), HttpStatus.BAD_REQUEST);
        }
        
        try {
            log.info("开始智能评分 - 目标汉字: {}", standardChar);
            
            // 使用混合评分：同时使用传统算法和AI评分
            return performHybridScoring(standardChar, userImage);
            
        } catch (ImageProcessingException e) {
            log.error("图像处理异常", e);
            return new ResponseEntity<>(Map.of("error", e.getMessage()), HttpStatus.INTERNAL_SERVER_ERROR);
        } catch (Exception e) {
            log.error("评分过程中发生错误", e);
            return new ResponseEntity<>(Map.of("error", "评分过程中发生错误"), HttpStatus.INTERNAL_SERVER_ERROR);
        }
    }

    /**
     * 智能评分：结合传统算法和AI评分
     * @param targetChar 目标汉字
     * @param userImage 用户手写汉字图片
     * @param method 评分方法：auto(自动选择)、traditional(传统算法)、ai(AI评分)、hybrid(混合评分)
     * @return 评分结果
     */
    @PostMapping("/smart-score")
    @Operation(summary = "智能评分：结合传统算法和AI评分")
    public ResponseEntity<Map<String, Object>> smartScore(
            @Parameter(description = "目标汉字", required = true, example = "学")
            @RequestParam("targetChar") String targetChar,
            
            @Parameter(description = "用户手写汉字图片", required = true)
            @RequestParam("userImage") MultipartFile userImage,
            
            @Parameter(description = "评分方法 (auto, traditional, ai, hybrid)", example = "auto")
            @RequestParam(value = "method", defaultValue = "auto") String method) {
        
        // 验证输入参数
        if (targetChar == null || targetChar.trim().isEmpty()) {
            return new ResponseEntity<>(
                Map.of("success", false, "error", "目标汉字不能为空"), 
                HttpStatus.BAD_REQUEST
            );
        }
        
        if (userImage == null || userImage.isEmpty()) {
            return new ResponseEntity<>(
                Map.of("success", false, "error", "请提供用户手写汉字图片"), 
                HttpStatus.BAD_REQUEST
            );
        }
        
        String contentType = userImage.getContentType();
        if (contentType == null || !contentType.startsWith("image/")) {
            return new ResponseEntity<>(
                Map.of("success", false, "error", "请提供有效的图片文件"), 
                HttpStatus.BAD_REQUEST
            );
        }
        
        try {
            log.info("开始智能评分 - 目标汉字: {}, 评分方法: {}", targetChar, method);
            
            switch (method.toLowerCase()) {
                case "traditional":
                    // 使用传统算法
                    Map<String, Object> traditionalResult = hanziScoreService.scoreHandwriting(targetChar, userImage);
                    traditionalResult.put("evaluationMethod", "TRADITIONAL_ALGORITHM");
                    traditionalResult.put("success", true);
                    return ResponseEntity.ok(traditionalResult);
                    
                case "ai":
                    // 使用AI评分
                    return ResponseEntity.ok(hanziAiScoreService.scoreWithAI(targetChar, userImage));
                    
                case "hybrid":
                case "auto":
                default:
                    // 混合评分：同时使用传统算法和AI，给出综合评价
                    return performHybridScoring(targetChar, userImage);
            }
            
        } catch (Exception e) {
            log.error("智能评分过程中发生错误 - 目标汉字: {}", targetChar, e);
            return new ResponseEntity<>(
                Map.of("success", false, "error", "评分过程中发生错误: " + e.getMessage()), 
                HttpStatus.INTERNAL_SERVER_ERROR
            );
        }
    }
    
    /**
     * 执行混合评分：结合传统算法和AI的结果
     */
    private ResponseEntity<Map<String, Object>> performHybridScoring(String targetChar, MultipartFile userImage) {
        try {
            // 保存图片用于调试
            ImageDebugUtils.saveImage(userImage, targetChar);

            // 同时获取传统评分和AI评分
            // Map<String, Object> traditionalResult = hanziScoreService.scoreHandwriting(targetChar, userImage);
            Map<String, Object> aiResult = hanziAiScoreService.scoreWithAI(targetChar, userImage);
            
            // 构建混合结果
            Map<String, Object> hybridResult = new HashMap<>();
            hybridResult.put("success", true);
            hybridResult.put("targetChar", targetChar);
            hybridResult.put("evaluationMethod", "AI_ANALYSIS_ONLY");
            
            // 传统评分结果
            /*
            hybridResult.put("traditional", Map.of(
                "totalScore", traditionalResult.get("totalScore"),
                "shapeScore", traditionalResult.get("shapeScore"),
                "strokeQualityScore", traditionalResult.get("strokeQualityScore"),
                "structureScore", traditionalResult.get("structureScore"),
                "aestheticScore", traditionalResult.get("aestheticScore"),
                "feedback", traditionalResult.get("feedback")
            ));
            */
            
            // AI评分结果
            if (Boolean.TRUE.equals(aiResult.get("success"))) {
                hybridResult.put("ai", Map.of(
                    "totalScore", aiResult.get("totalScore"),
                    "characterAccuracy", aiResult.get("characterAccuracy"),
                    "strokeStandard", aiResult.get("strokeStandard"),
                    "structureBalance", aiResult.get("structureBalance"),
                    "overallBeauty", aiResult.get("overallBeauty"),
                    "detailedFeedback", aiResult.get("detailedFeedback"),
                    "improvementSuggestions", aiResult.get("improvementSuggestions"),
                    "gradeLevel", aiResult.get("gradeLevel")
                ));
                
                // 仅使用AI分数
                Number aiScoreNum = (Number) aiResult.get("totalScore");
                int aiScore = aiScoreNum.intValue();
                int finalScore = aiScore;
                
                hybridResult.put("finalScore", finalScore);
                hybridResult.put("recommendation", "仅使用AI评分。");
            } else {
                // AI评分失败
                hybridResult.put("ai", Map.of("error", aiResult.get("error")));
                hybridResult.put("finalScore", 0);
                hybridResult.put("recommendation", "AI评分暂时不可用。");
            }
            
            return ResponseEntity.ok(hybridResult);
            
        } catch (Exception e) {
            log.error("混合评分失败", e);
            return new ResponseEntity<>(
                Map.of("success", false, "error", "混合评分失败: " + e.getMessage()), 
                HttpStatus.INTERNAL_SERVER_ERROR
            );
        }
    }
    
    /**
     * 生成混合评分的推荐意见
     */
    private String generateHybridRecommendation(int traditionalScore, int aiScore) {
        int scoreDiff = Math.abs(traditionalScore - aiScore);
        
        if (scoreDiff <= 5) {
            return "传统算法和AI评分结果一致，评分结果可信度较高。";
        } else if (scoreDiff <= 15) {
            return "传统算法和AI评分结果存在小幅差异，建议综合参考两个结果。";
        } else {
            return String.format("传统算法和AI评分结果差异较大（相差%d分），建议以AI评分为主参考。", scoreDiff);
        }
    }
}
